#include "global.h"

void myLog(wxString log)
{
 if(__DEBUG)wxLogMessage(log);
}
void debug(wxString log)
{
BFrame->SetStatusText(log);
}

wxString getDefaultConfigPath()
{
//current directory
wxString dir=::wxGetCwd();
//wxMessageBox(wxT("current dir:")+dir);
if(wxFile::Exists(dir+config))return dir;
//user home dire
dir=::wxGetHomeDir();
//wxMessageBox(wxT("wxGetHomeDir dir:")+dir);
return dir;
}
//static method
/*
   得到配置文件保存目录
*/
wxString getConfigFileDir()
{
wxString dir=getDefaultConfigPath();
//check 1.
return dir+config;
}
/*
根据key得到配置文件里的信息
*/
wxString readConfigItem(wxString key)
{
wxString result=wxEmptyString;
wxString fileName=getConfigFileDir();
//wxMessageBox(fileName);
if(!wxFile::Exists(fileName))
   {
       wxMessageBox(wxT("不能发现配置文件,必须首先配置!\n")+fileName);
       return result;
   }
wxFileInputStream is(fileName);
wxFileConfig *conf = new wxFileConfig(is,wxConvUTF8);
conf->Read(key,&result);
delete conf;
return result;
}

bool checkDatabase()
{
  wxString db=readConfigItem(wxT("Global/database"));
  if(db==wxEmptyString)
    {
      wxMessageBox(wxT("无法确定数据库位置，请首先试图建立配置！"));
     createDatabase();
     wxCommandEvent tmp;
     BFrame->configdatabase(tmp);
    // return false;
    db=readConfigItem(wxT("Global/database"));
    if(db==wxEmptyString)
    {
      wxMessageBox(wxT("建立配置文件")+getConfigFileDir()+wxT("不成功!\n无法运行!"));
      exit(1);
    }
    }
//   wxMessageBox(wxT("数据库地址:")+db);
  strcpy(DoubleBall::DB_LOCATION_HOME,db.mb_str(wxConvUTF8));
  return true;
}
/**
检查配置文件里的策略定义文件
*/
wxArrayString  checkAIStrategyName()
{
    wxArrayString  result;
  wxString name=readConfigItem(wxT("Strategy/name"));//

  if(name==wxEmptyString)
    {
      wxMessageBox(wxT("无法确定策略名称，请首先配置！"));
     return result;
    }
 wxStringTokenizer data(name,wxT(","));


 while ( data.HasMoreTokens() )
     {
      result.Add(data.GetNextToken());
     }
 return result;
}
/*
得到策略名字对应的class名字
*/
wxArrayString  checkAIStrategyClass()
{
    wxArrayString  result;
  wxString name=readConfigItem(wxT("Strategy/class"));
  if(name==wxEmptyString)
    {
      wxMessageBox(wxT("无法确定策略类，请首先配置！"));
     return result;
    }
 wxStringTokenizer data(name,wxT(","));
 while ( data.HasMoreTokens() )
     {
      result.Add(data.GetNextToken());
     }
 return result;
}
//static method over

wxString getLastTermOrder()
{

DoubleBall* db=new DoubleBall();

if(wxString::FromAscii(DoubleBall::_LastTermOrder).Len()==0)
  {
      db->initialize();
       if(wxString::FromAscii(DoubleBall::_LastTermOrder).Len()==0)return wxEmptyString;
  }
delete db;

wxString currentOrder=wxString::FromAscii(DoubleBall::_LastTermOrder);
wxString currentDate=getNextTermDate(wxString::FromAscii(DoubleBall::_LastTermDate));//term

   if(CHECK_YEAR_CHANGE(currentDate))
    {
       currentOrder=(currentDate.Mid(0,4));
       currentOrder=currentOrder+wxT("001");
    }else
    {
     currentOrder=getNextTermOrder(currentOrder);
    }
return currentOrder;
}

wxString getLastTermDate()
{
DoubleBall* db=new DoubleBall();

if(wxString::FromAscii(DoubleBall::_LastTermDate).Len()==0)
  {
      db->initialize();
  }
delete db;

return wxString::FromAscii(DoubleBall::_LastTermDate);

}

/*
得到下一期的日期
*/
wxString getNextTermDate(wxString lastdate)
{
 wxString result(wxT(""));
 if(lastdate.IsEmpty())lastdate=wxString::FromAscii(DoubleBall::_LastTermDate);

 wxArrayString datetimes=::wxStringTokenize(lastdate,wxT("-"));

 if(datetimes.Count()!=3)
 {
     wxLogMessage(wxT("时间格式不对,必须是年-月-日:")+lastdate);
 return wxEmptyString;
}
 long year,month,day;
 datetimes[0].ToLong(&year);
 datetimes[1].ToLong(&month);
 datetimes[2].ToLong(&day);
 struct tm sct;
 sct.tm_year  =(int)year;
 sct.tm_mon =(int)month;
 sct.tm_mday   =(int)day;

  wxDateTime fdt;
  fdt.ParseDate(lastdate.c_str());
//wxDateTime fdt= wxDateTime(sct);

switch(fdt.GetWeekDay())//Sun day is first
{
 case wxDateTime::Sun:fdt = fdt.Add(wxDateSpan::Days(2));break;
 case wxDateTime::Mon:fdt = fdt.Add(wxDateSpan::Days(1));break;
 case wxDateTime::Tue:fdt = fdt.Add(wxDateSpan::Days(2));break;
 case wxDateTime::Wed:fdt = fdt.Add(wxDateSpan::Days(1));break;
 case wxDateTime::Thu:fdt = fdt.Add(wxDateSpan::Days(3));break;
 case wxDateTime::Fri:fdt = fdt.Add(wxDateSpan::Days(2));break;
 case wxDateTime::Sat:fdt = fdt.Add(wxDateSpan::Days(1));break;
}

 result=fdt.Format(wxT("%Y-%m-%d"));;

 return result;
}
/*
返回cOrder的下一期的编号
*/
wxString getNextTermOrder(wxString cOrder)
{
 wxString result=wxEmptyString;
 if(cOrder.IsEmpty())cOrder=wxString::FromAscii(DoubleBall::_LastTermOrder);
unsigned long term;

 if(!cOrder.ToULong(&term))return wxEmptyString;//不是合格的数字
wxString year=cOrder.Mid(0,4);
 result=wxString::Format(wxT("%d"),term+1);
 return result;
}
/*
检查时间爱是否到了新的一年，如果是真编号需要从001开始
*/
bool  CHECK_YEAR_CHANGE(wxString termdate)
{
 wxString currentyear=wxString::FromAscii(DoubleBall::_LastTermDate).Mid(0,4);
  wxString thisyear=termdate.Mid(0,4);
  if(currentyear==thisyear)return false;
  return true;
}
/*
 查询_dbhistory结果格式化为HTML内容，term为链接
 compack ==true 压缩时间列
*/
wxString formatDBtoHTML(DoubleBall *db,bool compact)
{
 wxString result=wxEmptyString;

result=wxT("<table border=1 valign=top><tr><td >没有记录!</td></tr></table>");
 if(db->nrow==0)return result;
 result=wxEmptyString;

 wxString value=wxEmptyString;
//result=result+wxT("<html><body>");
 result=result+wxT("<table border=1>");
for(int i=1;i<=db->nrow;i++)//第一行为列名
  {
 result=result+wxT("<tr ")+(i%2==0?wxT(" BGCOLOR=#d3d3d3 "):wxEmptyString)+wxT(">");
     result=result+wxT("<td>")+wxString::Format(wxT("%02d"),i)+wxT("</td>");
    for(int j=0;j<db->ncol;j++) //第一列是rowid,去掉
        {
     if(compact && (j==1))continue;
    result=result+wxT("<td>");
       if(j>1)
        {
        value = wxString::Format(wxT("%02d"),atoi(db->records[i*db->ncol+j]));
         }else
         {
         value = wxString::FromAscii(db->records[i*db->ncol+j]);
         }

         if(j==0)
         {
         result=result+wxT("<a href=")+value+wxT(">")+value+wxT("</a>");
         }else if(j<db->ncol-1)
         {
         result=result+wxT("<font color=red><B>")+value+wxT("</B></font>");
         }else if(j==(db->ncol-1))
         {
            result=result+wxT("<font color=blue><B>")+value+wxT("</B></font>");
         }
        result=result+wxT("</td>");
        }
 result=result+wxT("</tr>");
  }
result=result+wxT("</table>");
//result=result+wxT("</body></html>");
return result;
}

/*
格式化LISP 数据库
*/
wxString formatLISPtoHTML(DoubleBall *db)
{
 wxString result=wxEmptyString;

result=wxT("<table border=1 valign=top><tr><td >没有记录!</td></tr></table>");
 if(db->nrow==0)return result;
 result=wxEmptyString;

 wxString value=wxEmptyString;
//result=result+wxT("<html><body>");
 result=result+wxT("<table border=1>");
for(int i=1;i<=db->nrow;i++)//第一行为列名
  {
 result=result+wxT("<tr>");
     result=result+wxT("<td>")+wxString::Format(wxT("%02d"),i)+wxT("</td>");
    for(int j=0;j<db->ncol;j++) //第一列是rowid,去掉
        {
         result=result+wxT("<td>");
         value = wxString::FromUTF8(db->records[i*db->ncol+j]);

         if(j==0)
         {
         result=result+wxT("<a href=")+value+wxT(">")+value+wxT("</a>");
         }else if(j<db->ncol-1)
         {
         result=result+wxT("<font color=red><B>")+value+wxT("</B></font>");
         }else if(j==(db->ncol-1))
         {
            result=result+wxT("<font color=blue><B>")+value+wxT("</B></font>");
         }
        result=result+wxT("</td>");
        }
 result=result+wxT("</tr>");
  }
result=result+wxT("</table>");
//result=result+wxT("</body></html>");
return result;
}
/*
把一个数据结果集格式化成类似wxGrid的方式
*/
wxString formatDBtoHTMLGrid(DoubleBall *db,int pagerows)
{

wxString result=wxEmptyString;
wxArrayString line;
wxString value=wxT("");
wxString redCSS=wxT("<font color=red><b>");
wxString redEnd=wxT("</b></font>");
wxString blueCSS=wxT("<font color=blue><b>");
wxString blueEnd=wxT("</b></font>");

 result=wxT("<table border=1>");
 int patch=pagerows-(db->nrow%pagerows);
 if(patch==pagerows)patch=0;//完全打印则跳过

 for(int i=1;i<=db->nrow ;i++) //first Line is columnn label =db->nrow
  {
      line.Clear();
 result=result+wxT("<tr ")+(i%2==0?wxT(" BGCOLOR=#d3d3d3 "):wxEmptyString)+wxT(">");
    //转换为wxArrayString
     for(int k=2;k<REDBALLNUMBER+2;k++)line.Add(wxString::Format(wxT("%02d"),atoi(db->records[i*db->ncol+k])));
  //term
    result=result+wxT("<td><font color=red><b>")+wxString::FromAscii(db->records[i*db->ncol])+wxT("</b></font></td>");
     for(int j=2;j<MAXREDBALL+2+1;j++)
     {
      result=result+wxT("<td>");
      if(j<MAXREDBALL+2)//red ball
      {
      value=wxString::Format(wxT("%02d"),j-1);
      if(line.Index(value)==wxNOT_FOUND)value=wxT("　");
      }else if(j==(MAXREDBALL+2))//blue ball
      {
       value=wxString::Format(wxT("%02d"),atoi(db->records[i*db->ncol+db->ncol-1]));
      }else
      {
       value=wxT("　");
      }
      result=result+(j==(MAXREDBALL+2)?blueCSS:redCSS)+value+(j==(MAXREDBALL+2)?blueEnd:redEnd)+wxT("</td></font>");
     }
   result=result+wxT("</tr>");
  }
//是否需要补充空行

for(int i=0;i<patch;i++)
 {
      result=result+wxT("<tr>");
// term=getNextTermOrder(term);
// term=wxString::Format(wxT("%02d"),i+1);
  for(int j=0;j<MAXREDBALL+3;j++)
   {
  if(j==1)continue;//date skip
  result=result+wxT("<td>");
       if(j==0)
        {
            value=wxT("_______");
        }else
         {
          value=wxT("　");
         }
  result=result+redCSS+value+redEnd+wxT("</td>");
   }
   result=result+wxT("</tr>");
 }
 result=result+wxT("</table>");
return result;
}

/*
把一个DB格式化为同wxGrid一样的情况，完全格式的打印
*/
wxString formatGridtoHTML(wxGrid * grid,int startrow,int offset,int pagenumber)
{
wxString page;
 wxString value;
 wxString blue=wxT("<font color=blue><b>");
 wxString blueEnd=wxT("</b></font>");

 wxString red=wxT("<font color=red><b>");
 wxString redEnd=wxT("</b></font>");

page=page+wxT("<table CELLSPACING=0 border=1>");
int patch = pagenumber-(offset%pagenumber);

if(patch==pagenumber)patch=0;//防止刚好打完。
//wxMessageBox(wxString::Format(wxT("startrow %02d,offset:%02d,pagenumber:%02d,patch:%02d"),startrow,offset,pagenumber,patch));

wxString term;
wxString shadowValue;

for(int i=0;i<offset;i++)
 {
     if((startrow+i)>(grid->GetNumberRows()-1))break;//skip
  //   if(!grid->IsVisible(startrow+i,0))break;//skip,inviseble.

      page=page+wxT("<tr>");
  for(int j=0;j<grid->GetNumberCols();j++)
   {
    if(j==0)term=grid->GetCellValue(startrow+i,j);
       if(j==1)continue;//date skip
  page=page+wxT("<td>");
    value=grid->GetCellValue(startrow+i,j);
    shadowValue=DoubleBallGridCellRenderer::DIRTTABLE->GetValue(startrow+i,j);
    debug(wxT("shadowvalue:")+shadowValue);
    if(DoubleBallGridCellRenderer::FILLEDBLANK && value==wxEmptyString && shadowValue!=wxEmptyString)
    {
    value=wxT("<font size=-2 color=#d3d3d3>")+shadowValue+wxT("</font>");
    red=redEnd=wxEmptyString;
    }else
    {
    red=wxT("<font color=red><b>");
    redEnd=wxT("</b></font>");
    }
  page=page+(j<grid->GetNumberCols()-1?red:blue)+value+(j<grid->GetNumberCols()-1?redEnd:blueEnd);
  page=page+wxT("</td>");
   }
   page=page+wxT("</tr>");
 }
//是否需要补充空行

for(int i=0;i<patch;i++)
 {
      page=page+wxT("<tr>");
 term=getNextTermOrder(term);
// term=wxString::Format(wxT("%02d"),i+1);
  for(int j=0;j<grid->GetNumberCols();j++)
   {
  if(j==1)continue;//date skip
  page=page+wxT("<td>");
       if(j==0)
        {
            value=term;
        }else
         {
          value=wxT("&nbsp;");
         }
  page=page+red+value+redEnd+wxT("</td>");
   }
   page=page+wxT("</tr>");
 }
 page=page+wxT("</table>");
 return page;
}
/*
 预测的表数据结构
*/
wxString formatNotestoHTML(DoubleBall *db)
{
 wxString result=wxEmptyString;

 if(db->nrow==0)return result;
 wxString value=wxEmptyString;
//wchar_t buf[1024];
//wxCSConv* conv=new wxCSConv():
 result=result+wxT("<table border=1>");
for(int i=1;i<=db->nrow;i++)//第一行为列名
  {
 result=result+wxT("<tr>");
     result=result+wxT("<td>")+wxString::Format(wxT("%02d"),i)+wxT("</td>");
    for(int j=0;j<db->ncol;j++) //第一列是rowid,去掉
        {
    result=result+wxT("<td><font color=red>");
//wxConvISO8859_1
         value = wxString::FromUTF8(db->records[i*db->ncol+j]);
        result=result+value+wxT("</font></td>");
        }
 result=result+wxT("</tr>");
  }
result=result+wxT("</table>");

return result;
}
/*
得到当前grid选中行偏离多少行offset的数据focusing row里的红色球
*/
wxArrayString getSelectedGridRowRedBall(wxGrid * grid,int offset)
{
wxArrayString result;

int row=0;
if(grid->GetCursorRow()==0)
{
    row=grid->GetNumberRows()-1+offset;
}else
{
 row=grid->GetCursorRow()+offset;
}

if(row!=0)
 {
  for(int i=2;i<grid->GetNumberCols()-1;i++)
   {
     wxString value=grid->GetCellValue(row,i);
     if(value!=wxEmptyString)
      {
      //wxLogMessage(value+wxT("\n"));
      int intvalue=atoi(value.mb_str());
      value=wxString::Format(wxT("%02d"),intvalue);
      result.Add(value);
      }
   }
 }

return result;
}

/* 格式化array to html string
*/
wxString formatArraytoHTML(wxArrayString result)
{
wxString buf;
buf=buf+wxT("<table border=1><tr>");
 for(int i=0;i<result.GetCount();i++)
   {
      buf=buf+wxT("<td> <font color=red><b>")+result.Item(i)+wxT("</b></font></td>");
   }
 buf=buf+wxT("</tr></table>");
return buf;
}
/* 格式化九宫图3X3,根据match里的数字来匹配
*/
wxString formatLUOSHU9(wxArrayString match)
{
 wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 result=result+wxT("<table border=1>");
  for(int i=0;i<3;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<3;j++)
          {
            value=LUOSHU9[i][j];
            if(
                match.GetCount()>0 &&
               match.Index(value.c_str())!=wxNOT_FOUND)
             {
               css=matchCSS;
              }else
               {
                 css  =wxEmptyString;
               }

              result=result+wxT("<td ")+css+wxT(">")+value+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}

/* 格式化九宫图3X3,根据match里的数字来匹配
*/
wxString formatLUOSHU16(wxArrayString match)
{
 wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 result=result+wxT("<table border=1>");
  for(int i=0;i<4;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<4;j++)
          {
            value=LUOSHU16[i][j];
            if(
               match.GetCount()>0 &&
               match.Index(value.c_str())!=wxNOT_FOUND)
             {
               css=matchCSS;
              }else
               {
                 css  =wxEmptyString;
               }

              result=result+wxT("<td ")+css+wxT(">")+value+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}
/* 格式化九宫图6X6,根据match里的数字来匹配
*/
wxString formatLUOSHU36InALL(wxArrayString records)
{
  int COLS=6;
// wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString matchCSS=wxT("<font color=red><b>");
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 wxString cssEnd    =wxEmptyString;
wxArrayString match ;
wxString title=wxEmptyString;
//create a array with all redball
if(records.GetCount()>0)
     title=records[0]+wxT(":<font color=red>");
long valuetmp=0;
wxString tmp=wxEmptyString;
long num=0;
 for(int i=2;i<records.GetCount()-1 && records.GetCount()>0;i++)
   {
     records[i].ToLong(&valuetmp,10);
     tmp=wxString::Format(wxT("%02d"),valuetmp);
     match.Add(tmp);//format redball
     title=title+tmp;
     if(i<records.GetCount()-2)title=title+wxT(",");
   }
  title=title+wxT("</font>");
  if(records.GetCount()>0)
     records[records.GetCount()-1].ToLong(&valuetmp,10);

  tmp=wxString::Format(wxT("%02d"),valuetmp);
 title=title+wxT("+<font color=blue>")+tmp+wxT("</font>");//blue
 result=result+wxT("<table border=1 width=130>");
  result=result+wxT("<tr><td colspan=")+wxString::Format(wxT("%02d"),COLS)+wxT(">")+title+wxT("</td></tr>");
  for(int i=0;i<COLS;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<COLS;j++)
          {
            value=LUOSHU36[i][j];
            if(match.GetCount()>0 && match.Index(value.c_str())!=wxNOT_FOUND)
             {
               css=matchCSS;
               cssEnd=wxT("</b></font>");
              }else
               {
                 css   =wxEmptyString;
                 cssEnd =wxEmptyString;
               }
value.ToLong(&num,10);
              result=result+wxT("<td")+(css==wxEmptyString?wxEmptyString:wxT(" bgcolor=yellow"))+wxT(">")+((num>33)?wxT("<font size=-2>")+value+wxT("</font>"):css+value +cssEnd)+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}

wxString DB2SingleCollect(DoubleBall *db)
{
  wxString result=wxEmptyString;

   for(int i=1;i<=db->nrow;i++)//skip firlst row is titile row
      {
         for(int j=2;j<db->ncol-1;j++)
           {
            result=result+(wxString::Format(wxT("%02d"),atoi(db->records[i*db->ncol+j])%10));
            if(j<db->ncol-1-1)result=result+wxT(",");
           }

      }
return result;
}
/*
把一个结果集合格式化为一个洛数
*/
wxString formatDB2LUOSHU36(DoubleBall *db,int PageSize)
{
  wxArrayString records;
  wxString CurrentPAGE;
  CurrentPAGE=wxT("<table border=1>");
   wxString eachline=wxEmptyString;
   int lackPage=  (PageSize-db->nrow%PageSize)%PageSize;
   if(lackPage==0 && db->nrow==0)lackPage=PageSize;

   for(int i=1;i<=db->nrow;i++)
      {
         for(int j=0;j<db->ncol;j++)
           {
            records.Add(wxString(db->records[i*db->ncol+j],wxConvUTF8));
           }

           if(i%3==1)
            {
             CurrentPAGE=CurrentPAGE+wxT("<tr>");
            }
            CurrentPAGE=CurrentPAGE+wxT("<td >");

            CurrentPAGE=CurrentPAGE+formatLUOSHU36InALL(records);
            CurrentPAGE=CurrentPAGE+wxT("</td>");
           if(i%3==0)
            {
             CurrentPAGE=CurrentPAGE+wxT("</tr>");
            }
           records.Clear();
         if(i==PageSize)break;
      }
  //补上空的行，一个page 15行
    records.Clear();
    records.Add(wxT("00"),DBHISTORY_COLS);
    records.Item(0)=wxT("_______");
     int dis=lackPage%3;//需要补充的列格数

     for(int i=0;i<dis;i++)
     {
            CurrentPAGE=CurrentPAGE+wxT("<td>");
             CurrentPAGE=CurrentPAGE+formatLUOSHU36InALL(records);
            CurrentPAGE=CurrentPAGE+wxT("</td>");
    }
    if(dis>0)
     CurrentPAGE=CurrentPAGE+wxT("</tr>");

    for(int i=1; i<=lackPage-dis;i++)
    {
          if(i%3==1)
            {
             CurrentPAGE=CurrentPAGE+wxT("<tr>");
            }
            CurrentPAGE=CurrentPAGE+wxT("<td width=120>");
            CurrentPAGE=CurrentPAGE+formatLUOSHU36InALL(records);
            CurrentPAGE=CurrentPAGE+wxT("</td>");
           if(i%3==0)
            {
             CurrentPAGE=CurrentPAGE+wxT("</tr>");
            }
    }
      CurrentPAGE=CurrentPAGE+wxT("</table>");
   return CurrentPAGE;
}
/* 格式化九宫图6X6,根据match里的数字来匹配

*/
wxString formatLUOSHU36(wxArrayString match,bool big)
{
  int COLS=6;
// wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString matchCSS=wxEmptyString;
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 wxString cssEnd    =wxEmptyString;
 matchCSS =matchCSS+wxT("<font color=red ")+(big?wxT(" size=+3"):wxEmptyString)+wxT("><u>");

 result=result+wxT("<table border=1>");
 long num=0;
  for(int i=0;i<COLS;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<COLS;j++)
          {
            value=LUOSHU36[i][j];

            if( match.GetCount()>0 && match.Index(value.c_str())!=wxNOT_FOUND)
             {
               css=matchCSS;
               cssEnd=wxT("</u></font>");
              }else
               {
                 css   =(big?wxT("<font size=+3>"):wxEmptyString);
                 cssEnd =(big?wxT(" </font>"):wxEmptyString);
               }
              result=result+wxT("<td>")+css+value +cssEnd+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}
/*
  根据本期match和上一期红球formermatch来分析趋势
*/
wxString formatLUOSHU36(wxArrayString match,wxArrayString formermatch,bool big)
{
  int COLS=6;
// wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString matchCSS=wxEmptyString;
 wxString formermatchCSS=wxEmptyString;
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 wxString cssEnd    =wxEmptyString;
 matchCSS       =matchCSS+wxT("<font color=red ")+(big?wxT(" size=+3"):wxEmptyString)+wxT("><u>");
 formermatchCSS =formermatchCSS+wxT("<font color=yellow")+(big?wxT(" size=+3"):wxEmptyString)+wxT("><STRIKE>");

 result=result+wxT("<table border=1>");
 long num=0;
 bool ffd=false;
  for(int i=0;i<COLS;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<COLS;j++)
          {
            value=LUOSHU36[i][j];
     //1.case
ffd=(  formermatch.GetCount()>0 && formermatch.Index(value.c_str())!=wxNOT_FOUND)?true:false;
            if( match.GetCount()>0 && match.Index(value.c_str())!=wxNOT_FOUND)
             {
               if(ffd)
               {
               css=formermatchCSS;
               cssEnd=wxT("</STRIKE></font>");
               }else
               {
               css=matchCSS;
               cssEnd=wxT("</u></font>");
               }
              }else
               {
                if(ffd)
                {
               css=formermatchCSS;
               cssEnd=wxT("</STRIKE></font>");
               }else
                {
                 css   =(big?wxT("<font size=+3>"):wxEmptyString);
                 cssEnd =(big?wxT(" </font>"):wxEmptyString);
                }
               }

              result=result+wxT("<td>")+css+value +cssEnd+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}

/* 格式化九宫图6X6,根据match里的数字来匹配
redBallHashMap里是预测要出区域
*/
wxString formatLUOSHU36WithSurround(wxArrayString match,redBallHashMap surround,bool big)
{
  int COLS=6;
// wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString matchCSS=wxEmptyString;
 wxString SRNDCSS=wxEmptyString;
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 wxString cssEnd    =wxEmptyString;

 matchCSS =matchCSS+wxT("<font color=red ")+(big?wxT(" size=+3"):wxEmptyString)+wxT(">");
// SRNDCSS = wxT(" bgcolor=YELLOW ");
 SRNDCSS = wxT(" ");
 bool isSRNDCSS=false;

 result=result+wxT("<table border=1>");
 long num=0;
  for(int i=0;i<COLS;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<COLS;j++)
          {
            value=LUOSHU36[i][j];
       isSRNDCSS =(surround.find(value) == surround.end()?false:true);
            if(match.GetCount()>0 && match.Index(value.c_str())!=wxNOT_FOUND)
             {
               css=matchCSS;
               cssEnd=wxT("</font>");
              }else
               {
                 css   =(big?wxT("<font size=+3>"):wxEmptyString);
                 cssEnd =(big?wxT(" </font>"):wxEmptyString);
               }
              result=result+wxT("<td ")+wxT(">")+css+(isSRNDCSS?wxT("<U>"):wxT(""))+value+(isSRNDCSS?wxT("</U>"):wxT("")) +cssEnd+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
 return result;
}
//format wxArrayString to wxString
wxString arrary2string(wxArrayString str)
{
 wxString result=wxEmptyString;
 for(int i=0;i<str.GetCount();i++)
    result=result+str[i]+(i<(str.GetCount()-1)?wxT(","):wxT(""));
return result;
}
wxString hashmap2string(redBallHashMap hm)
{
wxArrayString forecast;
  redBallHashMap::iterator it;
    for( it = hm.begin(); it !=hm.end(); ++it )
    {
       forecast.Add(it->first);
    }
    forecast.Sort(false);
return arrary2string(forecast);
}
wxArrayString hashmap2array(switchHashMap hm)
{
wxString result,key;
wxArrayString sortKey;
long value;
  switchHashMap::iterator it;
    for( it = hm.begin(); it !=hm.end(); ++it )
    {
       key=it->first;
       sortKey.Add(key);
    }
    sortKey.Sort();
return sortKey;
}

/*
转换为字符串
*/
wxString hashmap2string(switchHashMap hm)
{
wxString result,key;
wxArrayString sortKey;
long value;
  switchHashMap::iterator it;
    for( it = hm.begin(); it !=hm.end(); ++it )
    {
       key=it->first;
       sortKey.Add(key);
    }
    sortKey.Sort();
    for(int i=0;i<sortKey.GetCount();i++)
    {
     key=sortKey.Item(i);
     value=hm[key];
     result=result+key+wxT(":")+wxString::Format(wxT("%02d"),value)+wxT(" ");
    }

return result;
}

/*
格式化为HTML
*/
wxString hashmap2html(switchHashMap hm)
{
wxString result;
  switchHashMap::iterator it;
  wxString key;
wxArrayString sortKey;
long value;
  int max=0;
    for( it = hm.begin(); it !=hm.end(); ++it )
    {
       key=it->first;
       sortKey.Add(key);
    }
sortKey.Sort();
result=wxT("<table border=1><tr>");

//header
    for(int i=0;i<sortKey.GetCount();i++)
    {
       key=sortKey.Item(i);
      result=result+wxT("<td><font color=red><b>")+key+wxT("</b></font></td>");
       value=hm[key];
       if(max==0 ||max<value )max=value;
    }
result=result+wxT("</tr>");
result=result+wxT("<tr>");
//value
    for(int i=0;i<sortKey.GetCount();i++)
    {
     key=sortKey.Item(i);
     value=hm[key];
    result=result+wxT("<td>")+wxString::Format(wxT("%02d"),value)+wxT("</td>");
    }
result=result+wxT("</tr></table>");
return result;
}

/*
得到当前grid选中行货focusing row里的term
*/
wxString getSelectedGridRowTerm(wxGrid * grid,int offset)
{
wxString result;
int row=0;
if(grid->GetCursorRow()==0)
{
    row=grid->GetNumberRows()-1+offset;
}else
{
 row=grid->GetCursorRow()+offset;
}
if(row>0 && row< grid->GetNumberRows())
{
 row=row;
}else
{
row=0;
}

if(row!=0)
 {
  result=grid->GetCellValue(row,0);
 }
return result;
}
//得到当前行的篮球
wxString getSelectedGridRowBlueBall(wxGrid * grid,int offset)
{
wxString result;
int row=0;
if(grid->GetCursorRow()==0)
{
    row=grid->GetNumberRows()-1+offset;
}else
{
 row=grid->GetCursorRow()+offset;
}
if(row>0 && row< grid->GetNumberRows())
{
 row=row;
}else
{
row=0;
}

if(row!=0)
 {
  result=grid->GetCellValue(row,grid->GetNumberCols()-1);
 }
return result;
}
/*
设置Grid指定行的红球为指定的redball集合
*/
void setArraytoGridLine(wxGrid* grid,wxArrayString redball,int row)
{
 //clear redball zone
 for(int i=2;i<grid->GetNumberCols()-1;i++)
    grid->SetCellValue(row,i,wxEmptyString);

 for(int i=0;i<redball.GetCount();i++)
  {
   long value =0;
   redball[i].ToLong(&value,10);
   grid->SetCellValue(row,value+1,redball[i]);
  }
}

/*
 显示一个HTML对话框,返回用户的选择
*/
int showHTMLMessage(wxString info)
{
wxDialog* dlg =new wxDialog(NULL, wxID_ANY,wxT("Search Window"),
                 wxDefaultPosition, wxSize(wxGetDisplaySize().GetWidth()*0.8, wxGetDisplaySize().GetHeight()*0.8),
                            wxSYSTEM_MENU | \
             wxMINIMIZE_BOX | \
             wxCLOSE_BOX | \
             wxCAPTION | \
             wxCLIP_CHILDREN);



        wxBoxSizer *vboxPnl = new wxBoxSizer(wxVERTICAL);


    wxHtmlWindow * html = new wxHtmlWindow(dlg,ID_OPEN_HTMLDLG, wxPoint(10,10), wxSize(dlg->GetSize().GetWidth()-20,dlg->GetSize().GetHeight()-175), wxTAB_TRAVERSAL|wxWANTS_CHARS|wxHW_SCROLLBAR_AUTO|wxRESIZE_BORDER|wxMAXIMIZE_BOX  , wxT("COMPLEXAI"));
    html->SetBackgroundColour(*wxGREEN);
    wxString result=wxT("<html><body bgcolor=#c0c0c0>")
          +info
          +wxT("</body></html>");
    html->SetPage(result);
//wxButton *m_buttonOk = new wxButton(bgpanel, wxID_OK, wxT("OK"), wxDefaultPosition, wxSize(60,30), 0 );
 //wxSizer* sizer=dlg.CreateButtonSizer(wxOK|wxCANCEL);
 vboxPnl->Add(html, 0, wxALL|wxEXPAND, 10);
 wxBoxSizer *hboxPnl = new wxBoxSizer(wxHORIZONTAL );
 wxButton * ok = new wxButton(dlg, wxID_OK, L"确定");
     GlobalEvtHandler::CurrentPAGE=result;//for print
 wxButton * print = new wxButton(dlg, ID_BUTTON_PRINT_PAGE, L"打印");
 print->Connect(wxEVT_LEFT_DOWN,wxCommandEventHandler(GlobalEvtHandler::OnPagePrintHandler));
 hboxPnl->Add(ok, 0, wxCENTRE);
 hboxPnl->Add(print, 1, wxCENTRE);

 vboxPnl->Add(hboxPnl,0,wxCENTRE);

 dlg->SetSizer(vboxPnl);



vboxPnl->SetSizeHints(dlg);
     vboxPnl->Fit(dlg);
dlg->Show();
//int code=dlg.ShowModal();
// dlg.EndModal(code);
 return 1;
}

/*
用HTM窗口显示预测行和实际行的比较,
current:是当前数据
forcast:是预测数据
cTerm:是预测期号
ployName:是预测算法名称
*/
void displayForecast(wxArrayString current,wxArrayString forecast,wxString cTerm,wxString ployName)
{
wxString content=wxT("<table border=1>")
wxT("<thead><th></th><th></th><th>算法名称</th>")
wxT("<tr><td colspan=3>预测期号:")+cTerm+wxT("</td></tr>")
wxT("<tr><td align=right><b>当前数据:</b></td><td align=left>")+formatArraytoHTML(current)+wxT("</td><td>")+wxT("</td></tr>")
wxT("<tr><td align=right><b>预测数据:</b></td><td align=left>")+formatArraytoHTML(forecast)+wxT("</td><td><b><font color=red>")+ployName+wxT("</b></td></tr>")
wxT("</table>");
showHTMLMessage(content);
}
/*得到洛书36红球坐标
*/
wxPoint getLUOSHU36RedBallCoordinate(wxString redball)
{
 wxPoint result;
 result.x=-1;
 result.y=-1;
 for(int i=0;i<6;i++)
     {
         for(int j=0;j<6;j++)
           {
            if(LUOSHU36[i][j]==redball)
               {
                result.x=i;
                result.y=j;
                 return result;
               }
           }
     }
return result;
}
wxString getLUOSHU36Value(int row,int col)
{
 return LUOSHU36[row][col];
}

/*
发现包围矩阵
*/
redBallHashMap findLUOSHU36SurroundMatrix(wxArrayString redball)
{
 redBallHashMap result;
   wxPoint coor;//位置
   wxString value=wxEmptyString;
   int row,col,row1,col1;
   int target[6][6];
  redBallHashMap rarrays;
  wxString debug=wxEmptyString;

 for(int i=0;i<redball.GetCount();i++)
  {
   value=redball.Item(i);
   coor=getLUOSHU36RedBallCoordinate(value);
    row=coor.x;
    col=coor.y;

    result[value]=wxEmptyString;
    debug=debug+wxT("数字:[")+value+wxT("],")+value+wxT(",");

   if(row!=-1 && col!=-1)
     {
    target[row][col]=1;

       //upon
        row1=(row-1<0)?5:row-1;
        col1=col;
         result[LUOSHU36[row1][col1]]=wxEmptyString;
          debug=debug+LUOSHU36[row1][col1]+wxT(",");

     //left
        row1=row;
        col1=(col-1<0)?col1=5:col-1;
         result[LUOSHU36[row1][col1]]=wxEmptyString;
          debug=debug+LUOSHU36[row1][col1]+wxT(",");
    //right
        row1=row;
        col1=(col+1>5)?col1=0:col+1;
         result[LUOSHU36[row1][col1]]=wxEmptyString;
         debug=debug+LUOSHU36[row1][col1]+wxT(",");
     //bottom
        row1=(row+1>5)?0:row+1;
        col1=col;
         result[LUOSHU36[row1][col1]]=wxEmptyString;
         debug=debug+LUOSHU36[row1][col1]+wxT(",");
     //top left location
        row1=(row-1<0)?5:row-1;
        col1=(col-1<0)?5:col-1;
       result[LUOSHU36[row1][col1]]=wxEmptyString;
       debug=debug+LUOSHU36[row1][col1]+wxT(",");
     //top right
        row1=(row-1<0)?5:row-1;
        col1=(col+1>5)?0:col+1;
       result[LUOSHU36[row1][col1]]=wxEmptyString;
       debug=debug+LUOSHU36[row1][col1]+wxT(",");
     //bottom left
        row1=(row+1>5)?0:row+1;
        col1=(col-1<0)?5:col-1;
       result[LUOSHU36[row1][col1]]=wxEmptyString;
       debug=debug+LUOSHU36[row1][col1]+wxT(",");
    //bottom right
        row1=(row+1>5)?0:row+1;
        col1=(col+1>5)?0:col+1;
       result[LUOSHU36[row1][col1]]=wxEmptyString;
       debug=debug+LUOSHU36[row1][col1]+wxT(",");
     }
if(__DEBUG)wxLogMessage(debug);
     debug=wxEmptyString;
  }
   return result;
}

/*
redBallHashMap is forecast data redball,
real is actual number
*/
float forecastMatch(redBallHashMap map,wxArrayString real,bool isnumber)
{
 float percent=0.0;
 long count=0;
 wxString value=wxEmptyString;
 if(map.size()==0){wxLogMessage(wxT("map is 0!"));return percent;}
 if(real.GetCount()==0){wxLogMessage(wxT("real is 0!"));return percent;}

for(int i=0;i<real.GetCount();i++)
 {
  value=real.Item(i);
  if(map.find(value)!= map.end())count++;
 }

percent=(float)count/(float)real.GetCount();
if(isnumber)return count;
return percent;
}

/*发现预测中有匹配已知红色号码
*/
wxArrayString forecastMatch(wxArrayString source,wxArrayString target)
{

 wxArrayString result;

 const wxChar* value;

for(int i=0;i<source.GetCount();i++)
  {
    value = source.Item(i).c_str();
    if(target.Index(value)!=wxNOT_FOUND)
    {
     result.Add(value);//store match ball
    }
  }
return result;
}

/*发现预测中没有匹配已知红色号码
*/
wxArrayString forecastMatchMiss(redBallHashMap map,wxArrayString real)
{
 wxArrayString result;
 for(int i=0;i<real.GetCount();i++)
     result.Add(real.Item(i));
 result=real;

 int count=0;
 wxString value=wxEmptyString;
 if(map.size()==0){wxLogMessage(wxT("map is 0!"));return result;}
 if(real.GetCount()==0){wxLogMessage(wxT("real is 0!"));return result;}

for(int i=0;i<real.GetCount();i++)
 {
  value=real.Item(i);
  if(map.find(value)!= map.end())
  {
     myLog(value+wxT(" in result."));
     count=result.Index(value);
      result.RemoveAt(count);
  }
 }
return result;
}
/*
得到预测号码的被杀的号
*/
wxArrayString killLUOSHU36SurroundMatrix(redBallHashMap redball)
{
wxArrayString result;
wxString value=wxEmptyString;
if(redball.size()==0)return result;

  for(int i=1;i<=33;i++)
  {
      value=wxString::Format(wxT("%02d"),i);
   if(redball.find(value)==redball.end())result.Add(value);
  }
return result;
}

wxString testCaseLS()
{
wxString resultstr;
 wxArrayString result0;
 wxArrayString furture;
 wxArrayString miss;
redBallHashMap result;
wxString term;
 long value=99;
//::wxGetNumberFromUser(wxT("message"),wxT("输入最少多少期.."),&value,33);
float per=0.0;

for(int i=1;i<value;i++)
{


}
return resultstr;
}
/*
得到匹配的旗号,toolbar button
*/
void findMatchRedBall()
{

int width=BFrame->GetVirtualSize().GetWidth()-40;
int height=BFrame->GetVirtualSize().GetHeight()-20;
int barHeight=BFrame->GetToolBar()->GetToolSize().GetHeight();
int menuHeigh=BFrame->GetMenuBar()->GetVirtualSize().GetHeight();

//wxGetDisplaySize().GetWidth()*0.6
wxDialog* dlg =new wxDialog(NULL, wxID_ANY,wxT("Search Window"),
                 wxDefaultPosition, wxSize(width, height),wxSYSTEM_MENU | \
             wxMINIMIZE_BOX | \
             wxCLOSE_BOX | \
             wxCAPTION | \
             wxCLIP_CHILDREN);

wxTextValidator validator(wxFILTER_NUMERIC);

wxPanel* hpanel=new wxPanel(dlg, BFrame->ID_PANEL1, wxPoint(0,1), wxSize(width,height), wxTAB_TRAVERSAL|wxWANTS_CHARS|wxBORDER_DOUBLE , wxT("search"));
//add 对偶数
wxStaticText* slabel=new wxStaticText(hpanel,wxID_ANY, wxT("对偶数1"), wxPoint(5,1));
slabel->SetForegroundColour(*wxRED);
GlobalEvtHandler::startmatch = new wxTextCtrl(hpanel,wxID_ANY,wxEmptyString,wxPoint(53,1),wxSize(100,20),wxTE_LEFT);
GlobalEvtHandler::startmatch->SetToolTip(wxT("多个数字用,逗号隔开"));

wxStaticText* elabel=new wxStaticText(hpanel,wxID_ANY, wxT("对偶数2"), wxPoint(176,1));
elabel->SetForegroundColour(*wxRED);
 GlobalEvtHandler::endmatch=  new wxTextCtrl(hpanel,wxID_ANY,wxEmptyString,wxPoint(226,1),wxSize(100,20),wxTE_LEFT);
  GlobalEvtHandler::endmatch->SetToolTip(wxT("多个数字用,逗号隔开"));
//
	GlobalEvtHandler::h_comboBox1 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(5,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);
	GlobalEvtHandler::h_comboBox2 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(60,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);
	GlobalEvtHandler::h_comboBox3 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(110,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);
	GlobalEvtHandler::h_comboBox4 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(160,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);
	GlobalEvtHandler::h_comboBox5 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(215,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);
	GlobalEvtHandler::h_comboBox6 = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(265,30), wxSize(50,30), 34, REDBALLS, 0  ,validator);//wxCB_READONLY
//blue
	GlobalEvtHandler::h_blue_combobox = new wxComboBox( hpanel, wxID_ANY, wxEmptyString, wxPoint(330,30), wxSize(50,30), 17, BLUEBALLS, 0  ,validator);
GlobalEvtHandler::h_follow = new wxCheckBox(hpanel,wxID_ANY,wxT("看下一期"),wxPoint(390,5));
GlobalEvtHandler::h_positionStrict = new wxCheckBox(hpanel,wxID_ANY,wxT("位置对应"),wxPoint(390,25));
GlobalEvtHandler::h_positionStrict->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_watchNext = new wxComboBox(hpanel,wxID_ANY,listStype[0],wxPoint(475,5),wxSize(80,30),3,listStype,NULL);
GlobalEvtHandler::h_watchNext->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_watchNext->SetEditable(true);
wxStaticText* label=new wxStaticText(hpanel,wxID_ANY, wxT("开始期号"), wxPoint(405,45));
label->SetForegroundColour(*wxRED);
//485 start
    GlobalEvtHandler::searchstartterm = new wxTextCtrl(hpanel,wxID_ANY,wxEmptyString,wxPoint(475,40),wxSize(70,20),wxTE_LEFT);
    GlobalEvtHandler::searchstartterm->SetDefaultStyle(wxTextAttr(*wxRED));

wxButton*	searchButton  = new wxButton( hpanel,  wxID_ANY,  wxT("开始查询..."),wxPoint(575,30));
searchButton->Connect(wxEVT_LEFT_DOWN,wxCommandEventHandler(GlobalEvtHandler::OnSearchHandler));

wxButton*	copytoHTML  = new wxButton( hpanel,  wxID_ANY,  wxT("复制到粘贴板"),wxPoint(575,5));
copytoHTML->Connect(wxEVT_LEFT_DOWN,wxCommandEventHandler(bonusFrame::OnCopytoClipBoard));
wxStaticText* labelsql=new wxStaticText(hpanel,wxID_ANY, wxT("查询SQL"), wxPoint(675,5));
labelsql->SetForegroundColour(*wxRED);

//print
wxButton*	printHTML  = new wxButton( hpanel,  wxID_ANY,  wxT("打印..."),wxPoint(655,30));
  printHTML->Connect(wxEVT_COMMAND_BUTTON_CLICKED,wxCommandEventHandler(GlobalEvtHandler::OnPagePrintHandler));
//add sql
GlobalEvtHandler::sqltext = new wxTextCtrl(hpanel,wxID_ANY,wxEmptyString,wxPoint(735,5),wxSize(300,50),wxTE_LEFT);

GlobalEvtHandler::h_comboBox1->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));
GlobalEvtHandler::h_comboBox2->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));
GlobalEvtHandler::h_comboBox3->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));
GlobalEvtHandler::h_comboBox4->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));
GlobalEvtHandler::h_comboBox5->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));
GlobalEvtHandler::h_comboBox6->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));

GlobalEvtHandler::h_blue_combobox->SetFont(wxFont(10, wxDEFAULT, wxNORMAL, wxFONTWEIGHT_BOLD, 0, wxT("Sans")));

//set editor readonly
GlobalEvtHandler::h_comboBox1->SetEditable(true);
GlobalEvtHandler::h_comboBox2->SetEditable(true);
GlobalEvtHandler::h_comboBox3->SetEditable(true);
GlobalEvtHandler::h_comboBox4->SetEditable(true);
GlobalEvtHandler::h_comboBox5->SetEditable(true);
GlobalEvtHandler::h_comboBox6->SetEditable(true);
GlobalEvtHandler::h_blue_combobox->SetEditable(true);

GlobalEvtHandler::h_comboBox1->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_comboBox2->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_comboBox3->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_comboBox4->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_comboBox5->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_comboBox6->SetForegroundColour(*wxRED);
GlobalEvtHandler::h_blue_combobox->SetForegroundColour(*wxBLUE);
GlobalEvtHandler::h_follow->SetForegroundColour(*wxRED);

GlobalEvtHandler::h_historywin=new wxHtmlWindow(hpanel,ID_OPEN_HTMLDLG, wxPoint(5,60), wxSize(width-20,height-140), wxTAB_TRAVERSAL|wxWANTS_CHARS|wxHW_SCROLLBAR_AUTO, wxT(""));

GlobalEvtHandler::h_historywin->Connect(wxEVT_COMMAND_HTML_LINK_CLICKED,wxHtmlLinkEventHandler(bonusFrame::OnHtmlLinkClicked));



wxBoxSizer *vboxPnl = new wxBoxSizer(wxVERTICAL);
//wxButton *btnOk = new wxButton(dlg, wxID_CANCEL, wxT("&Ok"));
//GlobalEvtHandler::h_dialog = dlg;
//btnOk->Connect(wxEVT_LEFT_DOWN,wxCommandEventHandler(GlobalEvtHandler::DestroyDialog));

// wxSizer* sizer=dlg->CreateButtonSizer(wxOK|wxCANCEL);
 wxSizer* sizer=dlg->CreateButtonSizer(wxOK|wxCANCEL);

 vboxPnl->Add(hpanel, 0, wxALL|wxEXPAND, 10);
 vboxPnl->Add(sizer, 1,  wxCENTER);

 dlg->SetSizer(vboxPnl);

vboxPnl->SetSizeHints(dlg);
     vboxPnl->Fit(dlg);
//    dlg->Layout();
//      dlg->Centre();
// dlg->setto
 dlg->Show();//ShowModal();

}
/*
 得到连续数，2连,现在只考虑2连的问题
 并考虑循环问题,33和1也是连续数字
*/
fakeHTable  findContinuum(wxArrayString form)
{
fakeHTable  result;
long iam;
long next;
wxString nextStr;
wxString iamStr;
 for(int i=0;i<form.GetCount();i++)
   {
     iamStr  =form.Item(i);
     iamStr.ToLong(&iam,10);
     if(i==(form.GetCount()-1))
      {
      nextStr=form.Item(0);
      nextStr.ToLong(&next,10);
      }else
      {
      nextStr=form.Item(i+1);
      nextStr.ToLong(&next,10);
      }
      if(iam==(next-1))
         {
          wxArrayString r;
          r.Add(iamStr);
          r.Add(nextStr);
         result[iamStr]=r;
         }else if(iam==33 && next==1)
         {
          wxArrayString r;
          r.Add(iamStr);
          r.Add(nextStr);
         result[iamStr]=r;
         }
   }
//wxMessageBox(wxString::Format(arrary2string(form)+wxT("%02d"),result.GetCount()));
return result;
}

wxString getMinRedball(wxArrayString nums)
{
 nums.Sort(false);
 return nums.Item(0);
}
/*
 是否红球最大的数字
*/
wxString getMaxRedball(wxArrayString nums)
{
 nums.Sort(false);
 int max=nums.GetCount();
 return nums.Item(max-1);
}
#define BUFSIZE 8192
wxString AJAX(wxString _url)
{
wxString proxy=readConfigItem(wxT("Network/proxy"));
wxSocketBase::Initialize() ;
if(proxy!=wxEmptyString)
{
 //url.SetProxy(proxy);
 wxURL::SetDefaultProxy(proxy);
}

wxURL url(_url);
if(proxy!=wxEmptyString)
{
 //url.SetProxy(proxy);
 url.SetProxy(proxy);
}
BFrame->SetStatusText(wxT("准备访问:")+_url);
wxHTTP http;
wxString htmldata;
if(proxy!=wxEmptyString)
{
http.SetTimeout(5);
http.SetProxyMode(true);
}
   while (!http.Connect(url.GetServer()));
   wxSleep(1);
   wxApp::IsMainLoopRunning();
    size_t count=-1;
    wxInputStream *httpStream = url.GetInputStream();
    if (url.GetError() == wxPROTO_NOERR)
    {
    wxStringOutputStream out_stream(&htmldata);
    httpStream->Read(out_stream);
    wxDELETE(httpStream);
}
debug(wxString::Format(wxT("得到数据长度:%04d"),htmldata.Length()));
return htmldata;
}
/*异步方式得到数据
*/
wxString AJAX(wxString host,wxString _url)
{
BFrame->SetStatusText(wxT("准备访问:")+host+_url);
wxString proxy=readConfigItem(wxT("Network/proxy"));
if(proxy!=wxEmptyString)
{
 //url.SetProxy(proxy);
 BFrame->SetStatusText(wxT("Setup Proxy Server:")+proxy);
 wxURL::SetDefaultProxy(proxy);
}

wxHTTP http;
if(proxy!=wxEmptyString)
{
http.SetProxyMode(true);
}
else
{
 http.SetProxyMode(false);
}

wxString htmldata;//return
    size_t count=-1;

   http.SetTimeout(10);
   http.SetHeader(wxT("GET "),_url+wxT(" HTTP/1.1"));
   http.SetHeader(wxT("Content-type"), wxT("text/html; charset=utf-8"));
   http.SetHeader(wxT("REFERER"),host);
   http.SetHeader(wxT("User-Agent"),wxT("Mozilla/5.0 (Windows; U; Windows NT 5.1; zh-CN; rv:1.9.1.5) Gecko/20091102 Firefox/3.5.5"));
   while (!http.Connect(host));
   wxSleep(1);
   wxApp::IsMainLoopRunning();

   wxInputStream *httpStream =http.GetInputStream(_url);
    if (http.GetError() == wxPROTO_NOERR)
    {
    wxStringOutputStream out_stream(&htmldata);
    httpStream->Read(out_stream);
   wxDELETE(httpStream);
  }else
  {
    wxMessageBox(wxString::Format(wxT("network error:%02d,Server response:%02d"),http.GetError(),http.GetResponse()));
   }
debug(htmldata);
http.Close();
return htmldata;
}
/*
红蓝球霸获得所有数据,并返回比当前数据库内最后一期多的数据
*/
wxString HongLanQiuBa(wxString lastterm)
{

  wxString result1;
   wxString configurl=readConfigItem(wxT("Network/website1"));
  if(configurl==wxEmptyString)
    {
     configurl=(wxT("http://www.qiu8.cn/Update/his2010.html"));
      BFrame->SetStatusText(wxT("第一个没有发现配置地址!"));
    }
result1=AJAXBycurl(configurl);//AJAX(configurl);
  wxArrayString result;
  wxArrayString lastline;
  wxString tmp;
  wxString term=wxEmptyString;
    wxString value=wxEmptyString;

  if(result1!=wxEmptyString)
    {
        result1=result1.MakeUpper();
//     result1.Replace(wxT("<BR>"),wxEmptyString,true);
     int end=result1.find_last_of(wxT("<BR>"));//find last <br>
     tmp=result1.SubString(0,end-1);
      tmp.Replace(wxT("<BR>"),wxT(""));

     //::wxGetTextFromUser(wxEmptyString,wxEmptyString,tmp);
     result=::wxStringTokenize(tmp,wxT("\n"),wxTOKEN_RET_EMPTY_ALL);
// wxMessageBox(wxString::Format(result.Item(11)+wxT(" %02d"),result.GetCount()));
//     wxMessageBox(arrary2string(result));

        for(int i=(result.GetCount()-1);i>=0;i--)
       {
         value=result.Item(i);
        if(value==wxEmptyString){

            continue;
        }
         value.Replace(wxT("-"),wxT(" "));
         wxStringTokenizer tkz(value, wxT(":"));
         if(tkz.CountTokens()<2)continue;//防止数据格式错误
         wxString line;
            if( tkz.HasMoreTokens() )//得到第一个数字
            {
                line = tkz.GetNextToken();
            }
//         wxMessageBox(wxT("....")+line);
//        if(i==result.GetCount()-1)break;
         long first,second;
         lastterm.ToLong(&first,10);
         line.ToLong(&second,10);
         if(first>second)break;//skip not value
         if(first<=second)
         {
              term=value+(wxT("\n"))+term;
         }
       }
    }else
    {
     debug(configurl+wxT(" 没有得到数据!")+lastterm);
    }
  result1=term;
  wxString lastdate=getNextTermDate(wxEmptyString);

  result1.Replace(wxT(":"),wxT(" ")+lastdate+wxT(" "));
  return result1;
}
//www.58cp.com /kaijiangshuju/ssq.txt
//飞彩天下数据更新地址
wxString FeiCaiTianXia(wxString lastterm)
{
  wxString result1;
   wxString configurl=readConfigItem(wxT("Network/website2"));
  if(configurl==wxEmptyString)
    {
     //configurl=(wxT("http://www.58cp.com/kaijiangshuju/ssq.txt"));
     configurl=(wxT("http://www.17500.cn/getData/ssq.TXT"));
     //
      BFrame->SetStatusText(wxT("第二个没有发现配置地址!"));
    }
 result1=AJAXBycurl(configurl);//AJAX(configurl);

 wxArrayString result;
  wxString term=wxEmptyString;
  wxString value=wxEmptyString;

  if(result1!=wxEmptyString)
    {
  result=::wxStringTokenize(result1,wxT("\n"));
//  wxMessageBox(wxString::Format(wxT("%02d"),result.GetCount()));
   for(int i=(result.GetCount()-1);i>=0;i--)
   {
    value=result.Item(i);

    wxArrayString lastline=::wxStringTokenize(value,wxT(" "));
    wxString line=lastline.Item(0);
     long first,second;
     lastterm.ToLong(&first,10);
     line.ToLong(&second,10);
     if(first>second)break;//skip not value
     if(first<=second)
     {
          term=value+(wxT("\n"))+term;
     }

    }

    }else
    {
     debug(configurl+wxT(" 没有得到数据!"));
    }
  return term;
}
//http://www.17500.cn/getData/ssq.TXT
//乐彩网数据更新地址
wxString LeCaiWang(wxString lastterm)
{
  wxString result1;
   wxString configurl=readConfigItem(wxT("Network/website2"));
  if(configurl==wxEmptyString)
    {
     //configurl=(wxT("http://www.58cp.com/kaijiangshuju/ssq.txt"));
     configurl=(wxT("http://www.17500.cn/getData/ssq.TXT"));
     //
      BFrame->SetStatusText(wxT("第二个没有发现配置地址!"));
    }
 result1=AJAXBycurl(configurl);//AJAX(configurl);

 wxArrayString result;
  wxString term=wxEmptyString;
  wxString value=wxEmptyString;
  wxString term_data=wxEmptyString;

  if(result1!=wxEmptyString)
    {
  result=::wxStringTokenize(result1,wxT("\n"));
//  wxMessageBox(wxString::Format(wxT("%02d"),result.GetCount()));
   for(int i=(result.GetCount()-1);i>=0;i--)
   {
    value=result.Item(i);
    term=wxEmptyString;
    wxArrayString lastline=::wxStringTokenize(value,wxT(" "));
    wxString line=lastline.Item(0);
     long first,second;
     lastterm.ToLong(&first,10);
     line.ToLong(&second,10);
     if(first>second)break;//skip not value
     if(first<=second)
     {
      //get first 10 field value
      for(int tt=0;tt<9;tt++)
      {
       term=term+wxT(" ")+lastline.Item(tt);
      }
      term_data=term+(wxT("\n"))+term_data;
     }

    }

    }else
    {
     debug(configurl+wxT(" 没有得到数据!"));
    }
  return term_data;
}

wxString GetURLerror(wxURL url)
{
    wxString szError = wxEmptyString;
    switch(url.GetError())
    {
     case(wxURL_NOERR):
       szError = wxT("No Error Smile");
       break;
     case(wxURL_SNTXERR):
       szError = wxT("Syntax error in the URL string!");
       break;
     case(wxURL_NOPROTO):
       szError = wxT("Found no protocol which can get this URL!");
       break;
     case(wxURL_NOHOST):
       szError = wxT("An host name is required for this protocol!");
       break;
     case(wxURL_NOPATH):
       szError = wxT("A path is required for this protocol!");
       break;
     case(wxURL_CONNERR):
       szError = wxT("Connection error!");
       break;
     case(wxURL_PROTOERR):
       szError = wxT("An error occurred during negotiation!");
       break;
    }
    return wxT("wxURL ERROR:\n") + szError;
}

/*
 * Write data callback function (called within the context of
 * curl_easy_perform.
 */
static size_t write_data( void *buffer, size_t size, size_t nmemb, void *userp )
 {
  int segsize = size * nmemb;

  /* Check to see if this data exceeds the size of our buffer. If so,
   * set the user-defined context value and return 0 to indicate a
   * problem to curl.
   */
  if ( wr_index + segsize > MAX_BUF )
  {
    *(int *)userp = 1;
    return 0;
  }

  /* Copy the data from the curl buffer into our buffer */
  memcpy( (void *)&wr_buf[wr_index], buffer, (size_t)segsize );

  /* Update the write index */
  wr_index += segsize;

  /* Null terminate the buffer */
  wr_buf[wr_index] = 0;
//  wxMessageBox(wxString::Format(wxT("%010d,"),wr_index));
  return segsize;
 }

wxString AJAXBycurl(wxString url)
{
 wxString result=wxEmptyString;
//get proxy setting from registry
wxRegKey *pRegKey = new wxRegKey(wxT("HKEY_CURRENT_USER\\Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings"));
wxString key;
long enabled;
pRegKey->QueryValue(wxT("ProxyEnable"),&enabled);
if(enabled)
   {
    pRegKey->QueryValue(wxT("ProxyServer"),key);
   }
//red proxyserver is over

   CURL *curl;
  CURLcode ret;
   int  wr_error;

  /* First step, init curl */
  curl = curl_easy_init();
  if (!curl) {
    wxMessageBox(wxT("couldn't init curl\n"));
      return result;
  }
  BFrame->SetStatusText(wxT("当前地址:")+url);
   curl_easy_setopt(curl, CURLOPT_URL,(const char*) url.mb_str(wxConvUTF8));//url.c_str()

  curl_easy_setopt( curl, CURLOPT_WRITEDATA, (void *)&wr_error );
  curl_easy_setopt( curl, CURLOPT_WRITEFUNCTION, write_data );
  curl_easy_setopt(curl, CURLOPT_USERAGENT, "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1)");
  curl_easy_setopt(curl, CURLOPT_TIMEOUT,10);//10 second
//  curl_easy_setopt(curl, CURLOPT_HEADER,true);//verbose
  //curl_easy_setopt( curl, CURLOPT_PROXYTYPE, CURLPROXY_HTTP);
  wxString proxy=readConfigItem(wxT("Network/proxy"));
  if(proxy==wxEmptyString && key!=wxEmptyString)
     {
      if(wxMessageBox(wxT("系统Proxy Server已经设置:")+key+wxT("\n是否使用该代理?"),wxT("确认?"),wxYES_NO)==wxYES)
         {
          proxy=key;
         }
     }
  wxString proxyserver;
  long proxyport;
    if(proxy!=wxEmptyString)
    {
    BFrame->SetStatusText(wxT("setup proxy ")+proxy);
  wxStringTokenizer data(proxy,wxT(":"));
     if(data.CountTokens()<2)
     {
       wxMessageBox(wxT("proxy格式不对:[Network]\nproxy=10.11.1.1:80"));
       return wxEmptyString;
     }
     //get server
    if(data.HasMoreTokens() )
    {
        proxyserver = data.GetNextToken();
    }
     //get port
    if(data.HasMoreTokens() )
    {
        data.GetNextToken().ToLong(&proxyport,10);
    }
    curl_easy_setopt(curl, CURLOPT_HTTPPROXYTUNNEL, true);
    curl_easy_setopt(curl, CURLOPT_PROXY, (const char*) proxyserver.mb_str(wxConvUTF8));
    curl_easy_setopt(curl, CURLOPT_PROXYPORT, proxyport);
    }
  /* Allow curl to perform the action */
  ret = curl_easy_perform( curl );

 // wxMessageBox( wxString::Format(wxT("ret = %d (write_error = %d),Received bytes:%010d\n"), ret, wr_error,wr_index));

  /* Emit the page if curl indicates that no errors occurred */
  if ( ret == 0 )
  {
   result=wxString(wr_buf,wxCSConv(wxT("gb2312")));
  }else
  {
   wxMessageBox(wxString::Format(wxT("error code = %d (write_error = %d)\n"), ret, wr_error));
  }
  curl_easy_cleanup( curl );
 return result;
}
/*
统计最大，最小数，以及连续数出现最多次数
每个数字出现的频率
结果集合是select * from _DBHISTORY 抓出来的
*/
Statistics* statisticsRecords(DoubleBall * db)
{
 Statistics* result=new Statistics();
 long value,last=0,next=0,blue;
 wxString key;
 for(int i=1;i<=db->nrow;i++)
 {
//篮球统计
      wxString::FromAscii(db->records[i*db->ncol+db->ncol-1]).ToLong(&value,10);
      result->numberBlueCount[value-1]=result->numberBlueCount[value-1]+1;
//最大位置
      wxString::FromAscii(db->records[i*db->ncol+db->ncol-2]).ToLong(&value,10);
      result->numberMaxCount[value-1]=result->numberMaxCount[value-1]+1;
//最小位置
      wxString::FromAscii(db->records[i*db->ncol+2]).ToLong(&value,10);
      result->numberMinCount[value-1]=result->numberMinCount[value-1]+1;

//红球分析开始
    for(int j=2;j<db->ncol-1;j++)
    {
      wxString::FromAscii(db->records[i*db->ncol+j]).ToLong(&value,10);
 //得到区间划分
    result->Sorting(value);
//统计每个红球出现的次数
      result->numberCount[value-1]=result->numberCount[value-1]+1;
 //得到最小
      if(result->min==0 || result->min>value)
      {
       result->min=value;
      }
//得到最大
      if(result->max==0 || result->max<value)
      {
       result->max=value;
      }
    if(last==0){last=value;continue;}
     //得到连续
      if(value==(last+1))
      {
        key=wxString::Format(wxT("%02d-%02d"),last,value);
        if(result->continuum.find(key)== result->continuum.end())
          {
           result->continuum[key]=1;
          }else
          {
           result->continuum[key]=result->continuum[key]+1;;
          }
       }
        last=value;

    }
    last=0;
}
return result;
}
/*格式化一个数组
*/
wxString arrary2string(int num[],int len)
{
int wraplength=16;//Table 开始换行的开始
wxString result;
wxString nonzero=wxT("<font color=green size=+1><b>");
wxString nonzeroend=wxT("</b></font>");
result=wxT("<table border=1><tr>");
//Header
int max=0;
int wraplen=(len<=wraplength?len:wraplength);

///get max number
for(int i=0;i<len;i++)
{
if(max==0|| max<num[i])max=num[i];
}
for(int i=0;i<wraplen;i++)
{
result=result+wxT("<td><font color=red><b>")+wxString::Format(wxT("%02d"),i+1)+wxT("</b></font></td>");
}
result=result+wxT("</tr>");
//body content
result=result+wxT("<tr>");


for(int i=0;i<wraplen;i++)
{
result=result+wxT("<td>")+
(num[i]==max?wxT("<font color=red><b>"):(num[i]>0?nonzero:wxT("")))+
wxString::Format(wxT("%02d"),num[i])+
(num[i]==max?wxT("</b></font>"):(num[i]>0?nonzeroend:wxT("")))+
wxT("</td>");
}
result=result+wxT("</tr>");
//是否需要折行?
if(len>wraplength)
{
//wrap Header
result=result+wxT("<tr><td colspan=")+wxString::Format(wxT("%02d"),wraplen)+wxT("></td></tr>");
result=result+wxT("<tr>");
for(int i=1;i<=(len-wraplength);i++)
{
result=result+wxT("<td><font color=red><b>")+wxString::Format(wxT("%02d"),wraplen+i)+wxT("</b></font></td>");
}
result=result+wxT("<td colspan=")+wxString::Format(wxT("%d"),wraplen-(len-wraplength))+wxT(">")+wxT("</td>");
result=result+wxT("</tr>");
//wrap  body content
result=result+wxT("<tr>");
  for(int i=0;i<(len-wraplength);i++)
    {
    result=result+wxT("<td>")+
    (num[wraplength+i]==max?wxT("<font color=red><b>"):(num[wraplength+i]>0?nonzero:wxT("")))+
    wxString::Format(wxT("%02d"),num[wraplength+i])+
    (num[wraplength+i]==max?wxT("</b></font>"):(num[wraplength+i]>0?nonzeroend:wxT("")))+
    wxT("</td>");
    }
result=result+wxT("<td colspan=")+wxString::Format(wxT("%d"),wraplen-(len-wraplength))+wxT(">")+wxT("</td>");
result=result+wxT("</tr>");
}
result=result+wxT("</table>");
return result;

}

/*
得到红球之差的结果集合
*/
switchHashMap getRedballDistance(wxArrayString nums)//得到红球间隔数据
{
 long value1,value2,distance,maxmin;
 switchHashMap result;
 wxString item1,item2;
 wxString key;
 wxString maxvalue=getMaxRedball(nums);
 wxString minvalue=getMinRedball(nums);

  maxvalue.ToLong(&value1,10);
  minvalue.ToLong(&value2,10);

  maxmin=abs(33+value2-value1);//极端距离

 for(int i=0;i<nums.GetCount()-1;i++)
  {
   item1=nums.Item(i);
   item1.ToLong(&value1,10);

   item2=nums.Item(i+1);
   item2.ToLong(&value2,10);
   distance=abs(value2-value1);
   key=wxString::Format(wxT("%02d"),distance);
   if(result.find(key)==result.end())
   {
     result[key]=1;
   }else
   {
    result[key]=result[key]+1;
   }
  }
     key=wxString::Format(wxT("%02d"),maxmin);

   if(result.find(key)==result.end())
   {
     result[key]=1;
   }else
   {
    result[key]=result[key]+1;
   }
return result;
}

int getMinRedbalDistance(wxArrayString nums)
{
  wxString dis;
  long key;
switchHashMap distance=getRedballDistance(nums);
  switchHashMap::iterator it;
  int min=-1;
    for( it = distance.begin(); it !=distance.end(); ++it )
    {
       dis=it->first;
       dis.ToLong(&key,10);
       if(min==-1)min=key;
       if(key<min)min=key;
    }
return min;
}
/*
得到红球之和的数据
*/
switchHashMap getRedballSum(wxArrayString nums)
{
 long value1,value2,sum;
 switchHashMap result;
 wxString item1,item2;
 wxString key;
 for(int i=0;i<nums.GetCount()-1;i++)
  {
   item1=nums.Item(i);
   item1.ToLong(&value1,10);
 for(int j=i+1;j<nums.GetCount();j++)
  {
   item2=nums.Item(j);
   item2.ToLong(&value2,10);
   sum=value2+value1;
   if(sum>MAXREDBALL)continue;//>33 跳过
   key=wxString::Format(wxT("%02d"),sum);
   if(result.find(key)==result.end())
   {
     result[key]=1;
   }else
   {
    result[key]=result[key]+1;
   }
  }
  }
return result;
}
/*
发现两组书中都包含的数字
*/
wxString bothInclude(switchHashMap distance,switchHashMap sum)
{
if(sum.size()==0)return wxEmptyString;//所有的和可能都大于33，考虑特殊
wxString result,key;
  switchHashMap::iterator it;
    for( it = distance.begin(); it !=distance.end(); ++it )
    {
       key=it->first;
       if(sum.find(key)!= sum.end())result=result+key+wxT(",");
    }
return result;
}
/*
得到对应期的行号
*/
int  getGridRowLine(wxString term)
{
 int row=-1;
for(int i=0;i<BFrame->Grid1->GetNumberRows();i++)
{
  if(BFrame->Grid1->GetCellValue(i,0)==term)
   {
    row=i;
    break;
   }
}
 return row;
}

/*发现红球小于10的红球*/
wxArrayString findLessThanTen(wxArrayString form)
{
wxArrayString result;
form.Sort(false);
    wxString value;
    long num;
    for(int i=0;i<form.GetCount();i++)
     {
      value=form.Item(i);
      value.ToLong(&num,10);
      if(num<10)result.Add(value);
      if(num>=10)break;//排序决定了可以跳过去
     }
return result;
}
/*
从数字猜测对称数字,同num一起组合，num为最大数和次大数的差值
*/
wxArrayString guessCouble(wxArrayString numbs,int num)
{
// wxMessageBox(wxString::Format(arrary2string(numbs)+wxT("...")+wxString::Format(wxT("%02d"),num)));
 wxArrayString result;
 long value,guess;
 wxString key;


 for(int i=0;i<numbs.GetCount();i++)
   {
     key=numbs.Item(i);
     key.ToLong(&value,10);

     //开始猜测对成，

     guess=value*num;
     if(guess<=MAXREDBALL)result.Add(wxString::Format(wxT("%02d"),guess));

     //考虑斜线
     guess=num+value;
     if(guess<=MAXREDBALL)result.Add(wxString::Format(wxT("%02d"),guess));
     guess=abs(value-num);
     if(guess>0)result.Add(wxString::Format(wxT("%02d"),guess));

   }
 return result;
}
/*
猜测最左端小于10组合,目前采用组合方式
*/
wxArrayString guessLessThan10(wxArrayString numbs)//猜测最左端数字组合
{
 wxArrayString result;
 wxString laststr,nextstr;
 long last=0,next=0;
 long guess;
 for(int i=0;i<numbs.GetCount()-1;i++)
   {
       laststr=numbs.Item(i);
       laststr.ToLong(&last,10);
      for(int j=i+1;j<numbs.GetCount();j++)
       {
        nextstr=numbs.Item(j);
        nextstr.ToLong(&next,10);
        guess=last*10+next;
        if(guess<=MAXREDBALL)result.Add(wxString::Format(wxT("%02d"),guess));
        guess=next*10+last;
        if(guess<=MAXREDBALL)result.Add(wxString::Format(wxT("%02d"),guess));
       }
   }
 return result;
}
/*
得到红球记录最右边两个红球的距离
*/
int  getRightDistance(wxArrayString from)
{
from.Sort(false);
wxString right1,right2;
long r1,r2;
right1=from.Item(from.GetCount()-1);
right2=from.Item(from.GetCount()-2);
right1.ToLong(&r1,10);
right2.ToLong(&r2,10);
return abs(r1-r2);
}

wxString int2wxString(int n)
{
 return wxString::Format(wxT("%02d"),n);
}
string int2str (int n)
{
stringstream ss;
ss << n;
return ss.str();
}
string  combine(string * a, int n, int m)
{
 m = m > n ? n : m;
stringstream buffer;
 int* order = new int[m+1];
 for(int i=0; i<=m; i++)
  order[i] = i-1;

 int count = 0;

 int k = m;
 bool flag = true;
 while(order[0] == -1)
 {
  if(flag)
  {
   for(int i=1; i<=m; i++)
   {
//    cout << a[order[i]] << " ";
    buffer << a[order[i]]<<((i<m)?",":" ");
 }
   cout << endl;
   count++;
   flag = false;
  }

  order[k]++;
  if(order[k] == n)
  {
   order[k--] = 0;
   continue;
  }

  if(k < m)

  {
   order[++k] = order[k-1];
   continue;
  }

  if(k == m)
   flag = true;
 }

 delete[] order;
// cout<<buffer.str();
 return buffer.str();
}
/*
c++ string to wx
*/
wxArrayString split(wxString str,wxString splitter)
{
wxArrayString result;
// wxString str1(str.c_str(), wxConvUTF8);
//boost::split(strs, str, boost::is_any_of(" "))
 wxStringTokenizer data(str,splitter);
 while ( data.HasMoreTokens() )
     {
      result.Add(data.GetNextToken());
     }
return result;
}
/*
 得到某期号码得出的数字
*/
wxArrayString guessFolk(wxArrayString last)//根据上一期得到应该出的对应数
{
wxArrayString result;
 boolean has3=false;//包含个位有3的数字.3,13,23,33
 if(last.Index(wxT("03"))!=wxNOT_FOUND)has3=true;
 if(last.Index(wxT("13"))!=wxNOT_FOUND)has3=true;
 if(last.Index(wxT("23"))!=wxNOT_FOUND)has3=true;
 if(last.Index(wxT("33"))!=wxNOT_FOUND)has3=true;
if(has3)
{
    result.Add(wxT("03"));
    result.Add(wxT("13"));
    result.Add(wxT("23"));
    result.Add(wxT("33"));
}
return result;
}

wxString GraphOfArray(long values[],long length)
{
 wxString result=wxEmptyString;
 wxArrayString sorta;
 for(int i=0;i<length;i++)sorta.Add(wxString::Format(wxT("%02d"),values[i]));
 sorta.Sort(false);
 //wxLogMessage(arrary2string(sorta));
 wxString tmp;
 //数列法
 long distance=-1;
 long tmpdis;
 for(int i=1;i<length;i++)
  {
   tmpdis=abs(values[i]-values[i-1]);
   if(distance==-1){distance=tmpdis;continue;}
   if(tmpdis!=distance){break;result=wxEmptyString;}///不满足等间隔状态,
   result=wxT(".数列");
  }
  //差

  //X/法
  long a1,a2,a3;
  for(int i=2;i<length;i++)
  {
   sorta.Item(i-1).ToLong(&a2,10);
   sorta.Item(i-2).ToLong(&a1,10);
   sorta.Item(i).ToLong(&a3,10);
   if(a3==(a2+a1)){result=wxString::Format(wxT("%02d=%02d + %02d.和(差)模式"),a3,a2,a1);break;
    }else if(a3==(a2*a1)){result=wxString::Format(wxT("%02d=%02d * %02d 乘(除)模式"),a3,a2,a1);break;}
 //   else{result=wxEmptyString;break;}
  }
 return result;
}
/*
find source and target miss number.
*/
wxArrayString forecastMatchMiss(wxArrayString source,wxArrayString target)
{

 wxArrayString result;
 result = target;
 const wxChar* value;
 int begin=result.GetCount();
for(int i=0;i<source.GetCount();i++)
  {
    value = source.Item(i).c_str();
    result.Remove(value);
  }

return result;
}
void testECL()
{
wxApp * theApp = wxTheApp;
//wxMessageBox(wxString::Format(wxT("%02d"),theApp->argc));
//wxMessageBox((wxString(*theApp->argv)));
//char* para=wxString(*(theApp->argv)).char_str(wxConvUTF8);
//MessageBoxA(NULL,"0.",NULL,NULL);
//	char *anonymous = {0};
//  cl_boot(theApp->argc, &para);
  MessageBoxA(NULL,"1.",NULL,NULL);
/*
const char *lisp_code = "  \
 (progn \
   (defvar *old-terminal-io* *terminal-io*) \
   (defvar *old-error-output* *error-output*) \
   (setf *error-output* (make-broadcast-stream)) \
   (setf *terminal-io* (make-two-way-stream (make-string-input-stream "") (make-broadcast-stream))) \
 ) \
";

si_safe_eval(3,c_string_to_object(lisp_code), Cnil, OBJNULL);
*/
//  cl_object obj=c_string_to_object("\"Hello world你好\"");
//   wxMessageBox(wxString::Format(wxT("%s\n"),obj->string.self));
  MessageBoxA(NULL,"2.",NULL,NULL);
 // cl_pprint(1,obj);
  MessageBoxA(NULL,"3.",NULL,NULL);
 // cl_shutdown();
  MessageBoxA(NULL,"ECL work!",NULL,NULL);
}

//anylyst digits
//row term
wxString getDigitsTrendAnalyst(wxString term,int offset)
{
DoubleBall* db=new DoubleBall();

  wxString SQL=wxT("select rowid+")+wxString::Format(wxT("%02d"),offset)+wxT(" as rowid from _DBHISTORY where term='"+term+wxT("'"));
  wxString SQL2=wxT("select rowid from _DBHISTORY where term='"+term+wxT("'"));
  SQL=wxT("select * from _DBHISTORY where rowid> ("+SQL+wxT(") and rowid <=(")+SQL2+wxT(")"));
//wxGetTextFromUser(SQL,wxT("..."),SQL);
  db->query((SQL).char_str());

wxString result=wxEmptyString;

 if(db->nrow==0)return result;

vector<vector<wxString> > vMatrix(10);
   vector<wxString> level1;

 int value=0;
//result=result+wxT("<html><body>");
 result=result;//wxT("<table border=1>")

for(int i=1;i<=db->nrow;i++)//第一行为列名
  {
    for(int j=2;j<=db->ncol-2;j++)//去掉最后一列0
        {
        value = atoi(db->records[i*db->ncol+j]);
        vMatrix[value%10].push_back(wxString::Format(wxT("%02d"),value)
                                    +wxString::Format(wxT("(%d)"),db->nrow-i+1));
        }
  }
  result=result+wxT("<table border=1>")+wxT("<tr>")
  +wxT("<td><font size=+1><b>0</b></font></td>")
  +wxT("<td><font size=+1><b>1</b></font></td>")
  +wxT("<td><font size=+1><b>2</b></font></td>")
  +wxT("<td><font size=+1><b>3</b></font></td>")
  +wxT("<td><font size=+1><b>4</b></font></td>")
  +wxT("<td><font size=+1><b>5</b></font></td>")
  +wxT("<td><font size=+1><b>6</b></font></td>")
  +wxT("<td><font size=+1><b>7</b></font></td>")
  +wxT("<td><font size=+1><b>8</b></font></td>")
  +wxT("<td><font size=+1><b>9</b></font></td>")
  +wxT("</tr>");
  wxString section=wxEmptyString;
  result=result+wxT("<tr>");
 for(int i=0;i<10;i++)
 {
  result=result+wxT("<td valign=top>") ;
  section=wxEmptyString;
   level1 = vMatrix[i] ;
//      for(level2= level1.begin(); level2!= level1.end(); level2++)
//      {
for( int t=0;t<level1.size();t++)
  {
         section=section+level1[t];
        if(t<level1.size()-1)section=section+wxT("<br>|<br>");
  }

//      }
result=result+section+wxT("</td>") ;
 }
result=result+wxT("</tr></table>");

return result;
}
wxString getMissDistance(wxString term)
{
wxString maxrow=wxT("(select max(rowid) from _dbhistory)");
if(term !=wxEmptyString)
 {
   maxrow = wxT("(select rowid from _dbhistory where term='"+term+wxT("')"));
 }
wxString SQL=wxEmptyString;
SQL=wxT("SELECT ");
for(int i=1;i<=MAXREDBALL;i++)
{
SQL=SQL+
 maxrow+wxT("-")+wxT("(SELECT rowid from _dbhistory where ")+wxString::Format(wxT("%d"),i)+
               wxT("  in (red1,red2,red3,red4,red5,red6) ")+((term==wxEmptyString)?wxT(""):wxT(" and term<=")+term)+
               wxT(" order by term desc limit 1)")+
               wxString::Format(wxT("t%0d"),i)+((i<MAXREDBALL)?wxT(","):wxT(""));
}
wxLogMessage(SQL);
DoubleBall* db=new DoubleBall();

  db->query((SQL).char_str());
//wxGetTextFromUser(SQL);
wxString result=wxEmptyString;

 if(db->nrow==0)return result;
result=formatDBtoHTMLTable(db,MAXREDBALL);
return result;
}
wxString formatDBtoHTMLTable(DoubleBall *db,int len,int defaultwrap)
{
  wxString result=wxEmptyString;
int wraplength=defaultwrap;//Table 开始换行的开始

wxString nonzero=wxT("<font color=green size=+1><b>");
wxString nonzeroend=wxT("</b></font>");
result=wxT("<table border=1><tr>");
int wraplen=(len<=wraplength?len:wraplength);

  //header
  for(int i=0;i<wraplength;i++)
  {
   result = result+wxT("<td ><font color=red><b>");
   result=result+wxString::Format(wxT("%02d"),i+1);
   result = result +wxT("</b></font></td>");
  }
  result=result+wxT("</tr>");
   result=result+wxT("<tr>");
  //data
  for(int i=0;i<wraplength;i++)
  {
   result = result+wxT("<td>");
   result=result+ wxString::Format(wxT("%02d"),atoi(db->records[db->ncol+i]));
   result = result +wxT("</td>");
  }
result=result+wxT("</tr>");
if(len>wraplength)
{
//wrap Header
result=result+wxT("<tr><td colspan=")+wxString::Format(wxT("%02d"),wraplen)+wxT("></td></tr>");
result=result+wxT("<tr>");
//header2
for(int i=1;i<=(len-wraplength);i++)
{
result=result+wxT("<td><font color=red><b>")+wxString::Format(wxT("%02d"),wraplen+i)+wxT("</b></font></td>");
}
result=result+wxT("</tr>");
//wrap  body content
result=result+wxT("<tr>");
  for(int i=0;i<(len-wraplength);i++)
    {
    result=result+wxT("<td>")+
//    (num[wraplength+i]==max?wxT("<font color=red><b>"):(num[wraplength+i]>0?nonzero:wxT("")))+
    wxString::Format(wxT("%02d"),atoi(db->records[db->ncol+wraplength+i]))+
//    (num[wraplength+i]==max?wxT("</b></font>"):(num[wraplength+i]>0?nonzeroend:wxT("")))+
    wxT("</td>");
    }
result=result+wxT("</tr>");
}
  result = result+wxT("</table>");
  return result;
}
wxArrayString  guess20101005(wxString term)
{
 wxArrayString result;
 vector< guessRules > collect;
  wxString SQL5 = wxT("select * from _dbhistory where term <='")+term+wxT("' order by rowid desc limit 0,5");
  wxString SQL = wxT("select * from _dbhistory where term ='")+term+wxT("'");
DoubleBall* db =new DoubleBall();
db->query(SQL.char_str());
wxLogMessage(SQL);
wxLogMessage(SQL5);
BALL redballs[6] ={BALL(1),BALL(2),BALL(3),BALL(4),BALL(5),BALL(6)};

// wxLogMessage(wxString::Format(wxT("1:isEven   %d 2:isEven   %d 3:isEven  %d"),redballs[0].isEven(),redballs[1].isEven(),redballs[2].isEven()));
// wxLogMessage(wxString::Format(wxT("1:isPrime  %d 2:isPrime  %d 3:isPrime %d"),redballs[0].isPrime(),redballs[1].isPrime(),redballs[2].isPrime()));
// wxLogMessage(wxString::Format(wxT("1:isOdd    %d 2:isOdd    %d 3:isOdd    %d"),redballs[0].isOdd(),redballs[1].isOdd(),redballs[2].isOdd()));
// wxLogMessage(wxString::Format(wxT("1:isLow    %d 2:isLow    %d 3:isLow    %d"),redballs[0].isLow(),redballs[1].isLow(),redballs[2].isLow()));
// wxLogMessage(wxString::Format(wxT("1:isHigh   %d 2:isHigh   %d 3:isHigh   %d"),redballs[0].isHigh(),redballs[1].isHigh(),redballs[2].isHigh()));
// wxLogMessage(wxString::Format(wxT("1:isLonely %d 2:isLonely %d 3:isLonely %d"),redballs[0].isLonely(),redballs[1].isLonely(),redballs[2].isLonely()));
 //1.发现最大最小值
 wxLogMessage(wxT("1.发现最大最小值"));
 int maxint=0;
 int minint =0;
 int tmp =0;
 for(int i=2;i<db->ncol-1;i++)
    {

     tmp = atoi(db->records[db->ncol+i]);
     //
     redballs[i-2]= BALL(tmp);
     if(tmp>maxint)maxint = tmp;
     if(minint == 0 || tmp < minint)minint =tmp;
     wxLogMessage(wxString::Format(wxT("%02d"),maxint));
    }
wxLogMessage(wxT("1.发现最大最小值")+wxString::Format(wxT("%02d"),maxint));
  for(int i=0;i<6;i++)
    {
     if(redballs[i].getValue() == maxint )redballs[i].setHigh(true);
     if(redballs[i].getValue() == minint )redballs[i].setLow(true);
    }
for(int i=0;i<6;i++)
{
 wxString result =wxString::Format(wxT("Value:%02d,isHigh():%d\t,isLow():%d\t isLonely():%d\t isPrime():%d\t isEven():%d\t isOdd():%d\t"),redballs[i].getValue(),
                                    redballs[i].isHigh(),
                                    redballs[i].isLow(),
                                    redballs[i].isLonely(),
                                    redballs[i].isPrime(),
                                    redballs[i].isEven(),
                                    redballs[i].isOdd());
wxLogMessage(result);
}
vector< int > vector_1;
vector_1.push_back(maxint);
vector_1.push_back(minint);
guessRules first;

first.name =wxT("最大最小红球");
first.result = vector_1;
collect.push_back(first);
wxLogMessage(first.name+wxT(":")+wxString::Format(wxT("%02d size"),first.result.size()));
//2.发现连续数字数(得到间隔为1或2)  即较大数和较小数 相减的结果为1或2
//3.得到分区数字统计(得到每段内的High Key,Low Key,及孤立数),注意三连中间数字也属于孤立数
//4.如果5步得到孤立数字,根据4得到的连续数字组合,
//5.按段趋势.

delete db;
 return result;
}
/*得到一个数字最近5期最统计相伴出来最多的数字
*/
wxString formatNumberMate(wxString term,int range)
{
wxString resultstr=wxEmptyString;
DoubleBall * db=new DoubleBall();
 long value2,last=0,next=0;

//当前期
wxString SQL=wxT("select * from _DBHISTORY  where term ='")+term+wxT("'");
db->query(SQL.char_str());
 Statistics* result =findNumberMate(term,range);
wxString title;
    for(int j=2;j<db->ncol-1;j++)
    {
      wxString::FromAscii(db->records[1*db->ncol+j]).ToLong(&value2,10);
      title = title+wxT("<td>")+wxString::Format(wxT("%02d"),value2)+wxT("</td>");
      resultstr=resultstr+
        wxT("<td>")+wxString::Format(wxT("%02d"),result->numberCount[value2-1])+wxT("</td>");
    }
 //result

  title = wxT("<tr>")+title+wxT("</tr>");
  resultstr=wxT("<tr>")+resultstr +wxT("</tr>");
  resultstr =wxT("<table border=1><TH colspan=2>")+term+wxT("</th>")
                +title+resultstr+wxT("</table>");
return resultstr;
}

Statistics* findNumberMate(wxString term,int range)
{
wxString SQL=wxEmptyString;
//wxT("select * from _DBHISTORY  where term <'")+term+wxT("' order by term desc limit 0,5");
wxString SQL2=wxEmptyString;
DoubleBall * db=new DoubleBall();
DoubleBall * db2=new DoubleBall();
//db->query(SQL.char_str());
wxArrayString resultarr;
 Statistics* result=new Statistics();
  Statistics* lastresult=new Statistics();

 long value,last=0,next=0;
 long value2;
 wxString key;

//当前期
SQL=wxT("select * from _DBHISTORY  where term ='")+term+wxT("'");
db->query(SQL.char_str());
if(db->nrow==0)return result;//result is empty.

    wxString title=wxEmptyString;
    for(int j=2;j<db->ncol-1;j++)
    {
        result=new Statistics();
      wxString::FromAscii(db->records[1*db->ncol+j]).ToLong(&value2,10);

      SQL=wxT("select * from _dbhistory where ")+wxString::Format(wxT("%02d"),value2) +wxT(" in (red1,red2,red3,red4,red5,red6) ")
   +wxT(" union  select * from _dbhistory where rowid in (select rowid+1 from _dbhistory where ")
   + wxString::Format(wxT("%02d"),value2)+wxT("  in (red1,red2,red3,red4,red5,red6)) order by term desc limit 0,")
   +wxString::Format(wxT("%d"),range);
  //wxLogMessage(wxT(" findNumberMate:")+SQL);
    db2->query(SQL.char_str());
    //analyst

                     for(int i=1;i<=db2->nrow;i++)
                     {
                    //篮球统计
                          wxString::FromAscii(db2->records[i*db2->ncol+db2->ncol-1]).ToLong(&value,10);
                          result->numberBlueCount[value-1]=result->numberBlueCount[value-1]+1;
                    //最大位置
                          wxString::FromAscii(db2->records[i*db2->ncol+db2->ncol-2]).ToLong(&value,10);
                          result->numberMaxCount[value-1]=result->numberMaxCount[value-1]+1;

                    //红球分析开始
                        for(int j3=2;j3<db2->ncol-1;j3++)
                        {
                          wxString::FromAscii(db2->records[i*db2->ncol+j3]).ToLong(&value,10);
                     //统计每个红球出现的次数
                          if(value != value2)
                          result->numberCount[value-1]=result->numberCount[value-1]+1;
                        }
                    }
lastresult->numberCount[value2-1]=result->getMaxRedball();
    }

delete db2;
 delete db;
return lastresult;
}

wxString statis2string(DoubleBall *db,Statistics* st,wxString AIsql,bool display)
{
    wxString  HTML=wxEmptyString;

HTML=HTML+wxT("<table border=1>")
//    +wxT("<tr><td colspan=35><br><font color=green><b>条件:")+AIsql+wxT("</b></font></td></tr>")
    +(display?wxT("<tr><td colspan=35>")+formatDBtoHTML(db)+wxT("</td></tr>"):wxT(""))
    +wxT("<tr><td colspan=35 ><br><font color=green><b>各个数字出现频率统计:</b></font>")
    +wxT("<br><font color=red>红球出现频率统计:</font>")+arrary2string(&st->numberCount[0],MAXREDBALL)
    +wxT("<br><b><font color=blue>篮球出现频率统计:</font></b>")+arrary2string(&st->numberBlueCount[0],MAXBLUEBALL)
  //  +wxT("<br><font color=green><b>红球最大位置出现频率统计:</b></font>")
//    +arrary2string(&st->numberMaxCount[0],MAXREDBALL)+wxT("<br><font color=green><b>红球最小位置出现频率统计:</b></font>")
//    +arrary2string(&st->numberMinCount[0],MAXREDBALL)+wxT("<br>")
    +wxT("</td></tr>")
    +wxT("</table>");
    return HTML;
}
wxString formatLUOSHU36WithPredict(wxArrayString match,wxArrayString pred)
{
 wxLogMessage(wxT("last:")+arrary2string(match)) ;
 wxLogMessage(wxT("current:")+arrary2string(pred)) ;
  int COLS=6;
// wxString matchCSS=wxT(" style='font-weight:BOLD;background-color:red;color:white;'");
 wxString matchCSS=wxEmptyString;
  wxString matchPredCSS=wxEmptyString;
 wxString result =wxEmptyString;
 wxString value  =wxEmptyString;
 wxString css    =wxEmptyString;
 wxString cssEnd    =wxEmptyString;
 wxString cssPredEnd    =wxEmptyString;

 matchCSS =matchCSS+wxT("<font color=red><u>");
 matchPredCSS =matchCSS+wxT("<font color=blue><u>");
wxString duplicateCSS=wxT("<font color=yellow size=+1><u>");
 result=result+wxT("<table border=1>");
 long num=0;
 bool mflag=false;

  for(int i=0;i<COLS;i++)
    {
       result=result+wxT("<tr>");
       for(int j=0;j<COLS;j++)
          {
              css=wxEmptyString;
              mflag=false;
            value=LUOSHU36[i][j];

            if(match.GetCount()>0 && match.Index(value.c_str())!=wxNOT_FOUND)
             {
                 mflag=true;
               css=matchCSS;
               cssEnd=matchCSS;
               cssEnd=wxT("</u></font>");
              }
  //add prediction
            if( pred.GetCount()>0 && pred.Index(value.c_str())!=wxNOT_FOUND)
             {
              if(!mflag)
              {
               css=matchPredCSS;
              }else//has duplication
               {
                css=duplicateCSS;
               }
               cssEnd=wxT("</u></font>");
              }
              result=result+wxT("<td>")+css+value +cssEnd+wxT("</td>");
          }
        result=result+wxT("</tr>");
    }
   result=result+wxT("</table>");
  // wxLogMessage(result);
 return result;
}
Statistics* getSection(wxArrayString termdata)
{
 Statistics* st=new Statistics();
 wxString value=wxEmptyString;
long num=0;
 for(int i=0;i<termdata.GetCount();i++)
 {
   value = termdata.Item(i);
   value.ToLong(&num,10);
   st->Sorting((int)num);
 }
 return st;
}

wxString formatSection(wxArrayString termdata)
{
Statistics* st=getSection(termdata);
wxString result=wxEmptyString;
result=result+wxT("<table border=1><tr><td colspan=4><font color=red size=+2><b>段孤立数</b></font></td></tr><tr>")
      +wxT("<td>1-09</td>")
      +wxT("<td>10-19</td>")
      +wxT("<td>20-29</td>")
      +wxT("<td>30-33</td>")
      +wxT("</tr>");
//get numbers
result=result
       +wxT("<tr><td>")+(st->Section01_09.GetCount()==1?st->Section01_09.Item(0):wxT(""))+wxT("</td>")
       +wxT("<td>")+(st->Section10_19.GetCount()==1?st->Section10_19.Item(0):wxT(""))+wxT("</td>")
       +wxT("<td>")+(st->Section20_29.GetCount()==1?st->Section20_29.Item(0):wxT(""))+wxT("</td>")
       +wxT("<td>")+(st->Section30_33.GetCount()==1?st->Section30_33.Item(0):wxT(""))+wxT("</td></tr>");

result=result+wxT("</table>");
return result;
}
static int CompareStringLen(const wxString& first, const wxString& second)
{
 long value1,value2;
 first.ToLong(&value1,10);
 second.ToLong(&value2,10);
    return value1-value2;
}
//同其他红球间隔不为1，2，3的数字为孤立数
wxArrayString getIsolation(wxArrayString termdata)
{
 termdata.Sort(CompareStringLen);
 wxLogMessage(wxT("after sorted:")+arrary2string(termdata));
 wxString str;
 long value,value1,value2=0;
 wxArrayString isolate;//保存孤立数
 long isodis=3;//多大间隔才算孤立呢？
 for(int i=0;i<termdata.GetCount();i++)
 {
   str=termdata.Item(i);
  if(i==0 || i==(termdata.GetCount()-1))//首尾两个数字需要特殊处理一下
  {
    if(i==0)
    {
    termdata.Item(0).ToLong(&value,10);
    termdata.Item(termdata.GetCount()-1).ToLong(&value1,10);
    if((33+value)-value1<=isodis)
    {
    continue;
    }
    }
//last
    if(i==(termdata.GetCount()-1))
    {
    termdata.Item(i).ToLong(&value,10);
    termdata.Item(i-1).ToLong(&value1,10);
    if(value-value1>isodis)
    {
    isolate.Add(str);
    }
    }
  }
   if(i<termdata.GetCount()-1)
   {
    if(i>0)termdata.Item(i-1).ToLong(&value2,10);//previous,处理三连号
     str.ToLong(&value,10);
     termdata.Item(i+1).ToLong(&value1,10);
     if(value1-value>isodis && (i>0 && (value-value2)>isodis))//max distance
     {
      isolate.Add(str);
     }else if(value1-value>isodis && i==0 )//max distance
     {
      isolate.Add(str);
     }else
     {
      // i=i+1;//skip both number
       continue;
     }
   }

 }
 return isolate;
 wxLogMessage(wxT("isolate is:")+arrary2string(isolate));
}
wxString formatIsolation(wxArrayString termdata)
{
wxArrayString isodata=getIsolation(termdata);
wxString result=wxEmptyString;
 result=result+wxT("<table border=1><tr><td><font color=red size=+3><b>位置孤立数</b></font></td></tr>");
  result=result+wxT("<tr>");
 for(int i=0;i<isodata.GetCount();i++)
 {
   result=result+wxT("<td><b>")+isodata.Item(i)+wxT("</b></td>");
 }
 result=result+wxT("</tr></table>");
 return result;
}

wxString formatALLNumberMate(int range)
{
wxString resultstr=wxEmptyString;
DoubleBall * db=new DoubleBall();
 long value2,last=0,next=0;

//当前期

 Statistics* result =findALLNumberMate(range);
wxString title;
int wrapline=12;//12个数字就折行
wxString allstr;
       title=wxT("<tr>");
       resultstr=wxT("<tr>");
for(int j=1;j<=MAXREDBALL;j++)
    {
      if(j%12==0)
      {
        resultstr=resultstr+wxT("</tr>");
        title=title+wxT("</tr>");
       allstr=allstr+title+resultstr;
       title=wxT("<tr>");
       resultstr=wxT("<tr>");
      }
      title = title+wxT("<td><font color=red>")+wxString::Format(wxT("%02d"),j)+wxT("</font></td>");
      resultstr=resultstr+
        wxT("<td>")+wxString::Format(wxT("%02d"),result->numberCount[j-1])
          +wxT("<br>")+result->numberCountStr[j-1]
        +wxT("</td>");
        if(j%12!=0 && j==MAXREDBALL)
        {
        resultstr=resultstr+wxT("</tr>");
        title=title+wxT("</tr>");
       allstr=allstr+title+resultstr;
        }
    }
    allstr=wxT("<table border=1>")+allstr+wxT("</table>");
 //result

//  title = wxT("<tr><td></td><td>")+title+wxT("</td></tr>");
  allstr =wxT("<table border=1><TH colspan=2>每个红球同时在一期中出现概率统计</th><tr><td>")
                +allstr+wxT("</td></tr></table>");
return allstr;
}

/*
  发现出现同时出现概率最多的红球
*/
Statistics* findALLNumberMate(int range)
{
wxString SQL=wxEmptyString;
//wxT("select * from _DBHISTORY  where term <'")+term+wxT("' order by term desc limit 0,5");
wxString SQL2=wxEmptyString;
//DoubleBall * db=new DoubleBall();
DoubleBall * db2=new DoubleBall();
//db->query(SQL.char_str());
wxArrayString resultarr;
 Statistics* result=new Statistics();
  Statistics* lastresult=new Statistics();

 long value;
 wxString key;

    wxString title=wxEmptyString;
    for(int j=1;j<=MAXREDBALL;j++)
    {
        result=new Statistics();

      SQL=wxT("select * from _dbhistory where ")+wxString::Format(wxT("%02d"),j) +wxT(" in (red1,red2,red3,red4,red5,red6) ")
//   +wxT(" union  select * from _dbhistory where rowid in (select rowid+1 from _dbhistory where ")
//   + wxString::Format(wxT("%02d"),j)+wxT("  in (red1,red2,red3,red4,red5,red6)) ")
   +wxT("order by term desc limit 0,")
   +wxString::Format(wxT("%d"),range);
  //wxLogMessage(wxT(" findNumberMate:")+SQL);
    db2->query(SQL.char_str());
    //analyst

                     for(int i=1;i<=db2->nrow;i++)
                     {
                    //篮球统计
                          wxString::FromAscii(db2->records[i*db2->ncol+db2->ncol-1]).ToLong(&value,10);
                          result->numberBlueCount[value-1]=result->numberBlueCount[value-1]+1;
                    //最大位置
                          wxString::FromAscii(db2->records[i*db2->ncol+db2->ncol-2]).ToLong(&value,10);
                          result->numberMaxCount[value-1]=result->numberMaxCount[value-1]+1;

                    //红球分析开始
                        for(int j3=2;j3<db2->ncol-1;j3++)
                        {
                          wxString::FromAscii(db2->records[i*db2->ncol+j3]).ToLong(&value,10);
                     //统计每个红球出现的次数
                          if(value != j)
                          result->numberCount[value-1]=result->numberCount[value-1]+1;
                        }
                    }
lastresult->numberCount[j-1]=result->getMaxRedball();
lastresult->numberCountStr[j-1]=result->getMaxRedballs(j);
    }

delete db2;
// delete db;
return lastresult;
}
